package com.central.apps.handler.timeTask;

import com.central.app.common.quartz.QuartzJob;
import com.central.app.service.HandlerService;
import com.central.apps.dao.MaterialInventory.QueryDao;
import com.central.apps.entity.BlMessage;
import com.central.apps.service.MessageService;
import com.central.bizcommon.model.schedule.JobParams;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.collections.MapUtils;
import org.apache.commons.lang3.StringUtils;
import org.quartz.DisallowConcurrentExecution;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

import java.math.BigDecimal;
import java.math.BigInteger;
import java.text.DecimalFormat;
import java.text.NumberFormat;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.function.Function;
import java.util.stream.Collectors;

/**
 * 安全补货定时任务
 */
@Component
@Slf4j
//禁止并发执行(Quartz不要并发地执行同一个job定义（这里指一个job类的多个实例）)
@DisallowConcurrentExecution
public class SafeReplenishmentTask extends QuartzJob{

    @Autowired
    private HandlerService handlerService;
    @Autowired
    private MessageService messageService;

    //巡点检工单
    //格式: 秒 分 时 日 月 星期 年
    @SneakyThrows
    @Override
    public void executeJob(JobExecutionContext context, String jobnum, String jobname, List<JobParams> jobparams) {
        log.info("--------------开始检查物料是否要补货---------------");
        List<Map<String, Object>> bySql = handlerService.findBySql("select itemnum,loweststock,securitystock,description from gq_item");
        if(CollectionUtils.isNotEmpty(bySql)){
            for (Map<String, Object> map : bySql) {
                String itemnum = MapUtils.getString(map, "itemnum");
                String loweststock = MapUtils.getString(map, "loweststock");//最低库余量
                String securitystock = MapUtils.getString(map, "securitystock");//安全库余量
                String description = MapUtils.getString(map, "description");//物料描述
                List<Map<String, Object>> bySql1 = handlerService.findBySql("SELECT ROUND(SUM(curbaltotal),2) as sum from gq_inventory where itemnum = '" + itemnum + "'");
                Map<String, Object> map1 = bySql1.get(0);
                String sum = MapUtils.getString(map1, "sum");//现有库余量
                BigDecimal loweststockBig = new BigDecimal(loweststock!=null?loweststock:"0");
                BigDecimal sumBig = new BigDecimal(sum!=null?sum:"0");
                if(sumBig.compareTo(loweststockBig)==-1){
                    List<Map<String, Object>> bySql2 = handlerService.findBySql("SELECT id,nickname,field10,deptcode from sys_user where worknumber = (SELECT userworknumber from sys_role_user where rolecode = (SELECT code from sys_role where name= '一级库补库人员'))");
                    //计算申请采购数量   申请采购数量=安全库存量-现有库存量+在途采购量（已做采购订单，还未做接收）
                    String applyPurchaseNumber = applyPurchaseNumber(itemnum, sum, securitystock);

                    //现有余量小于最低库余量  生成补货物资采购申请单
                    String prnum = createPrApply(itemnum, applyPurchaseNumber, bySql2);

                    //给对应人员发送消息
                    sendMessage(bySql2,description,prnum);
                }
            }
        }

    }
    public String createPrApply(String itemnum,String applyPurchaseNumber,List<Map<String, Object>> bySql) throws Exception {
        //生成采购申请编号
        String prnumnew="";
        if(CollectionUtils.isNotEmpty(bySql)){
            Map<String, Object> map = bySql.get(0);
            String id = MapUtils.getString(map, "id");//需求人id
            String nickname = MapUtils.getString(map, "nickname");//需求人名
            int field10 = MapUtils.getIntValue(map, "field10");//人员台账id
            String deptcode = MapUtils.getString(map, "deptcode");//部门
            Map<String, Object> prMap = new HashMap<>();
            SimpleDateFormat df = new SimpleDateFormat("yyyy年MM月dd日");
            SimpleDateFormat datefmt = new SimpleDateFormat("yyyy-MM-dd");
            String format = df.format(new Date());
            StringBuilder stringBuilder = new StringBuilder();
            stringBuilder.append(format).append("补库申请");

            prMap.put("prdesc",stringBuilder.toString());
            prMap.put("createuserdesc",nickname);
            prMap.put("createuser",id);
            prMap.put("applyby",field10);
            prMap.put("applytime",datefmt.format(new Date()));
            prMap.put("attribute","无");
            prMap.put("type","1");
            prMap.put("deptcode",deptcode);
            prMap.put("status","新建");
            prMap.put("purchasecategory","物资");

//            List<Map<String, Object>> bySql3 = handlerService.findBySql("SELECT SUBSTR(prnum,5) as prnum from gq_pr ORDER BY prnum desc limit 1");
//            if(CollectionUtils.isNotEmpty(bySql3)){
//                Map<String, Object> map1 = bySql3.get(0);
//                int prnum = MapUtils.getIntValue(map1, "prnum");
//                prnum = prnum+1;
//                String s = prnumFigure(prnum);
//                StringBuilder stringBuilder1 = new StringBuilder();
//                prnumnew = stringBuilder1.append("CDPR"+s).toString();
//                prMap.put("prnum",prnumnew);
//            }
            //生成采购申请编号
            handlerService.addBizNum("prApp","gq_pr",prMap);
            BigInteger prid = (BigInteger)handlerService.insert("gq_pr",prMap);
            prnumnew = MapUtils.getString(prMap, "prnum");
            //采购物料明细行
            Map<String, Object> prlineMap = new HashMap<>();
            List<Map<String, Object>> bySql1 = handlerService.findBySql("select * from gq_item where itemnum = '" + itemnum + "'");
            if(CollectionUtils.isNotEmpty(bySql1)){
                Map<String, Object> map1 = bySql1.get(0);
                prlineMap.put("itemdesc",MapUtils.getString(map1,"description"));
                prlineMap.put("specifications",MapUtils.getString(map1,"specifications"));
                prlineMap.put("model",MapUtils.getString(map1,"model"));
                prlineMap.put("packform",MapUtils.getString(map1,"packform"));
                prlineMap.put("qualitygrade",MapUtils.getString(map1,"qualitygrade"));
                prlineMap.put("stexecunical",MapUtils.getString(map1,"stexecunical"));
                prlineMap.put("matergrade",MapUtils.getString(map1,"matergrade"));
                prlineMap.put("orderunit",MapUtils.getString(map1,"unit"));
                prlineMap.put("itemid",MapUtils.getString(map1,"id"));
                prlineMap.put("orderqty",applyPurchaseNumber);
                //取物料最新的历史价格
                String unitcost = "0";
                List<Map<String, Object>> bySql2 = handlerService.findBySql("SELECT unitcost from gq_hispricemater where itemnum = '" + itemnum + "' order by createtime desc LIMIT 1");
                if(CollectionUtils.isNotEmpty(bySql2)){
                    Map<String, Object> map2 = bySql2.get(0);
                    unitcost = MapUtils.getString(map2, "unitcost");//最新价格
                }
                prlineMap.put("unitcost",unitcost);
                prlineMap.put("linecost",new BigDecimal(unitcost).multiply(new BigDecimal(applyPurchaseNumber)).toString());
                prlineMap.put("occupnot","否");
                prlineMap.put("urgency","一般");
            }
            prlineMap.put("itemnum",itemnum);
            prlineMap.put("prid",prid.toString());
            prlineMap.put("deptcode",deptcode);
            prlineMap.put("applyby",String.valueOf(field10));
            prlineMap.put("createuser",id);
            prlineMap.put("prnum",prnumnew);
            prlineMap.put("purchasecategory","物资");
            handlerService.insert("gq_prline",prlineMap);
        }
        return prnumnew;
    }

    public String applyPurchaseNumber(String itemnum,String sum,String securitystock){
        //在途采购量
        List<Map<String, Object>> bySql = handlerService.findBySql("SELECT SUM(unreceivedqty) as count from gq_posline where itemnum = '" + itemnum + "'");
        Map<String, Object> map = bySql.get(0);
        String count = MapUtils.getString(map, "count");//在途采购量
        BigDecimal countBig = new BigDecimal(count==null?"0":count);
        BigDecimal sumBig = new BigDecimal(sum==null?"0":sum);//现有库余量
        BigDecimal securitystockBig = new BigDecimal(securitystock!=null?securitystock:"0");//安全库余量
        return securitystockBig.subtract(sumBig).add(countBig).toString();
    }

    public void sendMessage(List<Map<String, Object>> bySql1,String description,String prnum){
        List<Map<String, Object>> bySql = handlerService.findBySql("select messagenum from gq_message order by messagenum desc limit 1");
        String messagenum = "1001";
        if (CollectionUtils.isNotEmpty(bySql)) {
            Map<String, Object> map = bySql.get(0);
            messagenum = MapUtils.getString(map, "messagenum");
            Integer integer = Integer.valueOf(messagenum);
            int i = integer + 1;
            messagenum = String.valueOf(i);
        }
        if(CollectionUtils.isNotEmpty(bySql1)){
            BlMessage message = new BlMessage();
            message.setRecipient(MapUtils.getString(bySql1.get(0),"id"));
            message.setRecipientname(MapUtils.getString(bySql1.get(0),"nickname"));
            message.setCreatetime(new Date());
            message.setIsshow("未读");
            StringBuilder str = new StringBuilder();
            str.append("物料"+description+",现有库存低于最低库存，已生成补库采购申请"+prnum+"，请及时处理。");
            message.setContent(str.toString());
            message.setTitle("补库物资采购申请");
            message.setMessagenum(messagenum);
            message.setCreateuser(MapUtils.getString(bySql1.get(0),"id"));
            message.setCreateuserdesc(MapUtils.getString(bySql1.get(0),"nickname"));
            message.setStatus("未读");
            message.setVersion("1");
            int res = messageService.addMessage(message);
            System.out.println("添加状态:" + res);
        }
    }

    public String prnumFigure(int figure){
        NumberFormat numberFormat = NumberFormat.getInstance();
        numberFormat.setMaximumIntegerDigits(8);
        numberFormat.setMinimumIntegerDigits(8);
        return numberFormat.format(figure).replaceAll(",","");
    }
}
